package com.jack006.user.controller;

import com.jack006.api.BaseController;
import com.jack006.api.controller.user.UserControllerApi;
import com.jack006.exception.GraceException;
import com.jack006.grace.result.GraceJSONResult;
import com.jack006.grace.result.ResponseStatusEnum;
import com.jack006.pojo.AppUser;
import com.jack006.pojo.bo.UpdateUserInfoBO;
import com.jack006.pojo.vo.AppUserVO;
import com.jack006.pojo.vo.UserAccountInfoVO;
import com.jack006.user.service.UserService;
import com.jack006.utils.JsonUtils;
import com.netflix.hystrix.contrib.javanica.annotation.DefaultProperties;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.RestController;

import javax.validation.Valid;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

/**
 * @Classname UserController
 * @Description 用户信息相关接口实现类
 * @Date 2021-06-10 08:15
 * @Created by jack
 */
@RestController
@DefaultProperties(defaultFallback = "globalFallBack")
public class UserController extends BaseController implements UserControllerApi {

    final static Logger logger = LoggerFactory.getLogger(UserController.class);


    @Autowired
    private UserService userService;
    @Value("${server.port}")
    private String myPort;

    @Override
    public GraceJSONResult getUserInfo(String userId) {

        // 0、判断参数不能为空
        if (StringUtils.isBlank(userId)) {
            return GraceJSONResult.errorCustom(ResponseStatusEnum.UN_LOGIN);
        }

        AppUserVO appUserVO = getBasicUserInfo(userId);

        return GraceJSONResult.ok(appUserVO);
    }

    @Override
    public GraceJSONResult getAccountInfo(String userId) {

        // 0、判断参数不能为空
        if (StringUtils.isBlank(userId)) {
            return GraceJSONResult.errorCustom(ResponseStatusEnum.UN_LOGIN);
        }

        // 1、根据用户 ID 查询用户信息
        AppUser appUser = getUser(userId);
        UserAccountInfoVO accountInfoVO = new UserAccountInfoVO();
        BeanUtils.copyProperties(appUser,accountInfoVO);

        return GraceJSONResult.ok(accountInfoVO);
    }

    private AppUser getUser(String userId) {

        // 查询判断 redis 中是否包含用户信息，如果包含，则查询后直接返回，就不去查询数据库
        String userJson = redisOperator.get(REDIS_USER_INFO+":"+userId);
        AppUser appUser;
        if (StringUtils.isNotBlank(userJson)) {
            appUser = JsonUtils.jsonToPojo(userJson,AppUser.class);
        } else {
            appUser = userService.getUserById(userId);
            // 由于用户信息不怎么会变动，对于一些千万级别的网站来说，这类信息不会直接去查询数据库
            // 那么完全可以依靠 redis ,直接把查询的数据存入 redis 中
            redisOperator.set(REDIS_USER_INFO+":"+appUser.getId(), JsonUtils.objectToJson(appUser));
        }
        return appUser;
    }

    @Override
    public GraceJSONResult updateUserInfo(@Valid UpdateUserInfoBO updateUserInfoBO) {

        // 1、执行更新操作
        userService.updateUserInfo(updateUserInfoBO);

        return GraceJSONResult.ok();
    }

    @HystrixCommand
    @Override
    public GraceJSONResult queryByIds(String userIds) {

        //1、手动触发异常

//        int i = 1/0;

        //2、调用超时
//        try {
//            Thread.sleep(6000);
//        } catch (InterruptedException e) {
//            e.printStackTrace();
//        }

        if (StringUtils.isBlank(userIds)) {
            return GraceJSONResult.errorCustom(ResponseStatusEnum.USER_ID_IS_NULL_ERROR);
        }

        List<AppUserVO> publishList = new ArrayList<>();
        List<String> userIdList = JsonUtils.jsonToList(userIds, String.class);
        for (String userId : userIdList) {
            AppUserVO user = getBasicUserInfo(userId);
            publishList.add(user);
        }

        return GraceJSONResult.ok(publishList);

    }

    private AppUserVO getBasicUserInfo(String userId) {

        // 1、根据用户 ID 查询用户信息
        AppUser appUser = getUser(userId);

        // 2、返回用户信息
        AppUserVO appUserVO = new AppUserVO();
        BeanUtils.copyProperties(appUser,appUserVO);

        // 3.查询 redis 中用户的关注数和粉丝数，放到 userVo 渲染
        appUserVO.setMyFollowCounts(getCountsFormRedis(REDIS_MY_FOLLOW_COUNTS + ":" + userId));
        appUserVO.setMyFansCounts(getCountsFormRedis(REDIS_WRITER_FANS_COUNTS + ":" + userId));

        return appUserVO;
    }


}
